package com.example.shopping;

import android.app.ActionBar;
import android.app.Activity;
import android.app.AlertDialog;
import android.app.SearchManager;
import android.app.SearchableInfo;
import android.content.Context;
import android.content.DialogInterface;
import android.graphics.Color;
import android.os.Bundle;
import android.text.Editable;
import android.text.Html;
import android.text.InputFilter;
import android.text.InputType;
import android.text.TextWatcher;
import android.util.DisplayMetrics;
import android.view.Gravity;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.view.Window;
import android.view.WindowManager;
import android.widget.EditText;
import android.widget.LinearLayout;
import android.widget.ScrollView;
import android.widget.SearchView;
import android.widget.TableLayout;
import android.widget.TableRow;
import android.widget.TableRow.LayoutParams;
import android.widget.TextView;
import android.widget.Toast;

import com.example.shopping.api.SHDefaultParserDataManager;
import com.example.shopping.api.SHParserDataManager;
import com.example.shopping.api.SHResponseData;
import com.example.shopping.api.SHResponseInterface;
import com.example.shopping.api.SHShoppingAPI;
import com.example.shopping.parsers.SHProduceParserData;
import com.example.shopping.parsers.SHUpdateProduceParserData;
import com.example.shopping.shdatas.SHError;
import com.example.shopping.shdatas.SHProduce;
import com.example.shopping.shdatas.SHSuccessMessage;
import com.example.shopping.tableview.adapter.SHListProduce;

import java.util.ArrayList;
import java.util.List;


public class MainActivity extends Activity implements SearchView.OnQueryTextListener{

    private SHParserDataManager parserDataManager;
    private SHShoppingAPI shoppingAPI;
    private SHListProduce listProduce;
    static int limitItemCd = 13;
    private float[] colWidthPersent;
    private String[] colLabel;
    private int screenWidth;
    LinearLayout linearLayoutParent;
    private TableLayout tableLayout;

    private SearchView mSearchView;
    private TextView mStatusView;

    private MenuItem menuItemProcess;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        getWindow().requestFeature(Window.FEATURE_ACTION_BAR);

        //init shopping api
        parserDataManager = new SHDefaultParserDataManager();
        parserDataManager.addParseData(new SHProduceParserData());
        parserDataManager.addParseData(new SHUpdateProduceParserData());
        shoppingAPI = new SHShoppingAPI(parserDataManager);
        listProduce = new SHListProduce();


        colWidthPersent = new float[]{ 0.055f, 0.26f, 0.14f, 0.14f, 0.07f, 0.07f, 0.07f, 0.1f, 0.1f};
        colLabel = new String[]{"番号", "商品名", "メーカー名","取引先名","商品区分","税区分","数量","原単価", "売単価"};

        // get width screen of device
        DisplayMetrics metrics = new DisplayMetrics();
        getWindowManager().getDefaultDisplay().getMetrics(metrics);

        screenWidth = metrics.widthPixels;//0.10


        // create layout parent
        linearLayoutParent = new LinearLayout(this);
        linearLayoutParent.setOrientation(LinearLayout.VERTICAL);
        linearLayoutParent.setLayoutParams(new LayoutParams(android.view.ViewGroup.LayoutParams.MATCH_PARENT, android.view.ViewGroup.LayoutParams.MATCH_PARENT));


        // create header
        TableLayout tableLayoutHeader = createHeader(colWidthPersent, colLabel, screenWidth);
        linearLayoutParent.addView(tableLayoutHeader);

        //init tableView
        tableLayout =  initTableView(listProduce,colWidthPersent, colLabel, screenWidth, linearLayoutParent);


        mStatusView = new TextView(this);

        setContentView(linearLayoutParent);

        ActionBar actionBar = getActionBar();
        actionBar.setTitle("アンドロイドのサンプルソフト");

    }

    @Override
    protected void onResume() {
        super.onResume();
    }

    private void requestProcess(boolean show){
        if(menuItemProcess != null){
            menuItemProcess.setVisible(show);
        }
    }

    /**
     *
     * @param colWidthPersent
     * @param colLabel
     * @param screnWidth
     * @return
     */
    private TableLayout createHeader(float[] colWidthPersent, String[] colLabel, int screnWidth){

        TableLayout tableLayout = new TableLayout(getApplicationContext());
        TableRow tableRow;
        TextView textView;

        for (int i = 0; i < 1; i++) {
            tableRow = new TableRow(getApplicationContext());
            tableRow.setLayoutParams(new TableRow.LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT));
            tableRow.setBackgroundResource(R.drawable.header_border);
            tableRow.setBackgroundColor(getResources().getColor(R.color.background_header));
            for (int j = 0; j < colLabel.length; j++) {
                textView = new TextView(getApplicationContext());
                textView.setLayoutParams(new LayoutParams(android.view.ViewGroup.LayoutParams.MATCH_PARENT, android.view.ViewGroup.LayoutParams.MATCH_PARENT));
                textView.setWidth((int) (colWidthPersent[j] * screnWidth));
                textView.setText(colLabel[j]);
                textView.setBackgroundColor(Color.BLUE);
                textView.setTextColor(Color.WHITE);
                textView.setShadowLayer(1, 0, -1, getResources().getColor(R.color.color_shadown));
                textView.setGravity(Gravity.CENTER);
                textView.setTextSize(15.0f);
//                textView.setSingleLine(true);
                textView.setBackgroundResource(R.drawable.header_border);
                textView.setPadding(1, 10, 1, 10);
                tableRow.addView(textView);
            }
            tableLayout.addView(tableRow);
        }

        return tableLayout;

    }

    /**
     *
     * @param shListProduce
     * @param colWidthPersent
     * @param colLabel
     * @param screnWidth
     * @param parent
     */
    private TableLayout initTableView(SHListProduce shListProduce, float[] colWidthPersent, String[] colLabel, int screnWidth, LinearLayout parent){

        TableLayout tableLayoutBody = new TableLayout(getApplicationContext());
        tableLayoutBody.setLayoutParams(new TableLayout.LayoutParams(TableLayout.LayoutParams.MATCH_PARENT, TableLayout.LayoutParams.MATCH_PARENT));

        // set length produce
        ArrayList produce = shListProduce.getArrayList();
        int lent = produce.size();

        for (int i = 0; i < lent; i++) {
            TableRow tableRowBody = new TableRow(getApplicationContext());
            tableRowBody.setLayoutParams(new TableRow.LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT));
            //tableRowBody.setBackgroundResource(R.drawable.border);
            if(i % 2 == 0){
                tableRowBody.setBackgroundColor(getResources().getColor(R.color.background_body_1));
            }else{
                tableRowBody.setBackgroundColor(getResources().getColor(R.color.background_body_2));
            }
            for (int j = 0; j < colLabel.length; j++) {
                TextView textViewBody = new TextView(getApplicationContext());
                textViewBody.setLayoutParams(new LayoutParams(android.view.ViewGroup.LayoutParams.MATCH_PARENT, android.view.ViewGroup.LayoutParams.MATCH_PARENT));
                textViewBody.setWidth((int)(colWidthPersent[j]*screnWidth));
                textViewBody.setText(String.valueOf(((ArrayList) (produce.get(i))).get(j)));
                textViewBody.setBackgroundColor(Color.BLUE);
                textViewBody.setTextColor(Color.BLACK);
                textViewBody.setGravity(Gravity.CENTER);
                textViewBody.setBackgroundResource(R.drawable.border);
                textViewBody.setPadding(3, 10, 3, 10);
                tableRowBody.addView(textViewBody);
            }
            tableLayoutBody.addView(tableRowBody);
        }

        // crate ScrollView wrap table layout body
        ScrollView scoScrollingTable = new ScrollView(this);
        scoScrollingTable.setLayoutParams(new LayoutParams(android.view.ViewGroup.LayoutParams.MATCH_PARENT, android.view.ViewGroup.LayoutParams.MATCH_PARENT));
        scoScrollingTable.addView(tableLayoutBody);

        LinearLayout linearLayout = new LinearLayout(this);
        linearLayout.setLayoutParams(new LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, android.view.ViewGroup.LayoutParams.WRAP_CONTENT));
        linearLayout.addView(scoScrollingTable);

        parent.addView(linearLayout);
        return tableLayoutBody;

    }

    public void updateTableView(final SHListProduce shListProduce, final float[] colWidthPersent, final String[] colLabel, final int screnWidth, final LinearLayout parent){
        TableLayout tableLayoutBody = tableLayout;
        tableLayoutBody.removeAllViews();

        // set length produce
        final ArrayList produce = shListProduce.getArrayList();
        int lent = produce.size();

        for (int i = 0; i < lent; i++) {
            final int finalI = i;
            final TableRow tableRowBody = new TableRow(getApplicationContext());
            tableRowBody.setLayoutParams(new TableRow.LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT));
            //tableRowBody.setBackgroundResource(R.drawable.border);
            if(i % 2 == 0){
                tableRowBody.setBackgroundColor(getResources().getColor(R.color.background_body_1));
            }else{
                tableRowBody.setBackgroundColor(getResources().getColor(R.color.background_body_2));
            }
            for (int j = 0; j < colLabel.length; j++) {
                final int jj = j;
                if(j == 6) {
                    runOnUiThread(new Runnable() {
                        @Override
                        public void run() {
                            final EditText textViewBody = new EditText(getApplicationContext());
                            textViewBody.setInputType(InputType.TYPE_CLASS_NUMBER);
                            textViewBody.setLayoutParams(new LayoutParams(android.view.ViewGroup.LayoutParams.MATCH_PARENT, android.view.ViewGroup.LayoutParams.MATCH_PARENT));
                            textViewBody.setWidth((int) (colWidthPersent[jj] * screnWidth));
                            textViewBody.setText(String.valueOf(((ArrayList) (produce.get(finalI))).get(jj)));
                            textViewBody.setTextColor(Color.BLACK);
                            textViewBody.setGravity(Gravity.CENTER);
                            textViewBody.setTag(shListProduce.objectAddIndex(finalI));
                            textViewBody.setTextSize(15);
                            textViewBody.setHint("0");
                            InputFilter[] inputFilters = new InputFilter[]{new InputFilter.LengthFilter(5)};
                            textViewBody.setFilters(inputFilters);
                            textViewBody.setBackgroundResource(R.drawable.edittext_modified_states);
                            textViewBody.setPadding(3, 10, 3, 10);
                            textViewBody.addTextChangedListener(new TextWatcher() {
                                public void afterTextChanged(Editable s) {
                                    Object pro = textViewBody.getTag();
                                    if (pro != null && pro instanceof SHProduce) {
                                        SHProduce shProduceOld = (SHProduce) pro;
                                        if (s.length() > 0) {
                                            shProduceOld.orderQty = Integer.parseInt(s.toString());
                                        } else {
                                            shProduceOld.orderQty = 0;
                                        }
                                    }
                                }

                                public void beforeTextChanged(CharSequence s, int start, int count, int after) {
                                }

                                public void onTextChanged(CharSequence s, int start, int before, int count) {
                                    if (s.length() == 0) {
                                        textViewBody.setError("数量を入力してください");
                                    }
                                }
                            });
                            textViewBody.setOnFocusChangeListener(new View.OnFocusChangeListener() {
                                @Override
                                public void onFocusChange(View v, boolean hasFocus) {
                                    if(textViewBody.length() > 0)
                                        textViewBody.setSelection(textViewBody.length());
                                }
                            });
                            tableRowBody.addView(textViewBody);
                        }
                    });
                }else{
                    TextView textViewBody = new TextView(getApplicationContext());
                    textViewBody.setLayoutParams(new LayoutParams(android.view.ViewGroup.LayoutParams.MATCH_PARENT, android.view.ViewGroup.LayoutParams.MATCH_PARENT));
                    textViewBody.setWidth((int) (colWidthPersent[j] * screnWidth));
                    textViewBody.setText(String.valueOf(((ArrayList) (produce.get(i))).get(j)));
                    textViewBody.setBackgroundColor(Color.BLUE);
                    textViewBody.setTextColor(Color.BLACK);
                    if(j == 1 || j == 2 || j == 3){
                        textViewBody.setGravity(Gravity.LEFT);
                    }else{
                        textViewBody.setGravity(Gravity.CENTER);
                    }
                    textViewBody.setBackgroundResource(R.drawable.border);
                    textViewBody.setPadding(3, 10, 3, 10);

                    tableRowBody.addView(textViewBody);
                }

            }
            tableLayoutBody.addView(tableRowBody);
        }

    }
    private void hideDefaultKeyboard() {
        getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_HIDDEN);//u have got lot of methods here
    }
    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        MenuInflater inflater = getMenuInflater();
        inflater.inflate(R.menu.main, menu);
        MenuItem searchItem = menu.findItem(R.id.action_search);
        mSearchView = (SearchView) searchItem.getActionView();
        mSearchView.setQueryHint(Html.fromHtml("<font color=#CC80CC>" + "商品コードを入力してください" + "</font>"));
        mSearchView.setInputType(InputType.TYPE_CLASS_NUMBER | InputType.TYPE_NUMBER_VARIATION_NORMAL);
        int id = mSearchView.getContext().getResources().getIdentifier("android:id/search_src_text", null, null);
        TextView textView = (TextView) mSearchView.findViewById(id);
        textView.setTextColor(Color.WHITE);

        // setup search item
        setupSearchView(searchItem);

        menuItemProcess = menu.findItem(R.id.action_request_process);
        menuItemProcess.setVisible(false);

        return true;
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {

        switch (item.getItemId()){
            case R.id.action_saves:{
                updateProduce();
                hideDefaultKeyboard();
                break;
            }
            case R.id.action_clear:{
                if(listProduce != null && listProduce.count() != 0){
                    AlertDialog.Builder builder = new AlertDialog.Builder(this);
                    builder.setTitle("メッセージ");
                    builder.setMessage("表示しているデータをクリアします。よろしいですか?");

                    builder.setNegativeButton("いいえ", new DialogInterface.OnClickListener() {
                        @Override
                        public void onClick(DialogInterface dialogInterface, int i) {
                            dialogInterface.dismiss();
                        }
                    }).setNeutralButton("はい", new DialogInterface.OnClickListener() {
                        @Override
                        public void onClick(DialogInterface dialogInterface, int i) {
                            listProduce.removeAll();
                            tableLayout.removeAllViews();
                        }
                    });

                    AlertDialog alertDialog = builder.create();
                    alertDialog.show();

                }
                break;
            }
        }
        return super.onOptionsItemSelected(item);
    }

    private void setupSearchView(MenuItem searchItem) {

        if (isAlwaysExpanded()) {
            mSearchView.setIconifiedByDefault(false);
        } else {
            searchItem.setShowAsActionFlags(MenuItem.SHOW_AS_ACTION_IF_ROOM
                    | MenuItem.SHOW_AS_ACTION_COLLAPSE_ACTION_VIEW);
        }

        SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);
        if (searchManager != null) {
            List<SearchableInfo> searchables = searchManager.getSearchablesInGlobalSearch();

            SearchableInfo info = searchManager.getSearchableInfo(getComponentName());
        }

        mSearchView.setOnQueryTextListener(this);
    }

    public boolean onQueryTextChange(String newText) {
        if(newText.length()>limitItemCd){
            mSearchView.setQuery(newText.substring(0,limitItemCd), false);
        }
        mStatusView.setText("Query = " + newText);
        return false;
    }

    public boolean onQueryTextSubmit(String query) {
        mStatusView.setText("Query = " + query + " : submitted");
        searchProduce(formatSearchString(query));
        return true;
    }

    public boolean onClose() {
        mStatusView.setText("Closed!");
        return false;
    }

    protected boolean isAlwaysExpanded() {
        return false;
    }

    private String getMessageError(int code, String produceCode){
        switch (code){
            case 0: return " 不明エラーが発生しました。";
            case 400: return "入力した商品コードが検索できませんでした。";
            case 402: return "入力した値のフォーマットが正しくなかった。";
            case 403: return "数量が保存できませんでした。";
            case 404: return String.format( "入力した商品コード「%s」が検索できません。", produceCode);
        }
        return "Error";
    }

    public void searchProduce(final String produceId) {
        requestProcess(true);
        final Activity myActivity = this;
        shoppingAPI.searchItem(produceId, new SHResponseInterface() {
            @Override
            public void responseData(Object sender, int statusCode, final SHResponseData responseData) {
                requestProcess(false);
                if (responseData != null && responseData.getClass().equals(SHError.class)){
                    runOnUiThread(new Runnable() {
                        @Override
                        public void run() {
                            Toast toast = Toast.makeText(myActivity, getMessageError(((SHError) responseData).statusCode, produceId), Toast.LENGTH_LONG);
                            toast.setGravity(Gravity.TOP|Gravity.CENTER_HORIZONTAL, 0, 0);
                            toast.show();
                        }
                    });
                    return;
                }
                SHProduce produce = (SHProduce)responseData;
                if (produce != null){
                    listProduce.addObject(produce);

                    //show
                    updateTableView(listProduce, colWidthPersent, colLabel, screenWidth, linearLayoutParent);
                }
            }

            @Override
            public void responseDataFail(Object sender, int statusCode, final Throwable err, final Object errorResponse) {
                requestProcess(false);
                runOnUiThread(new Runnable() {
                    @Override
                    public void run() {
                        Toast toast = Toast.makeText(myActivity, "不明エラーが発生しました", Toast.LENGTH_LONG);
                        toast.setGravity(Gravity.TOP|Gravity.CENTER_HORIZONTAL, 0, 0);
                        toast.show();
                    }
                });
                return;

            }
        });
    }

    public void updateProduce() {

        ArrayList<SHProduce> arrayList = listProduce.getProductListHasChange();

        if (arrayList.size() == 0) return;
        requestProcess(true);
        final Activity myActivity = this;
        final int sumUpdate = arrayList.size();
        final int[] failCount = {0};
        final int[] successCount = {0};
        for (int i = 0; i < arrayList.size(); i++){
            final SHProduce produce = arrayList.get(i);
            shoppingAPI.saveItem(produce.itemCd, produce.orderQty+"", new SHResponseInterface() {
                @Override

                public void responseData(Object sender, int statusCode, final SHResponseData responseData) {
                    if (responseData != null && responseData.getClass().equals(SHError.class)){
                        SHError error = (SHError)responseData;
                        if (error.statusCode <= 0 || error.statusCode > 200){
                            failCount[0]++;
                            updateStatus();
                            return;
                        }
                    }
                    final SHSuccessMessage message = (SHSuccessMessage)responseData;
                    if (message != null){
                        produce.updateOldProduce();
                        successCount[0]++;
                    }else{
                        failCount[0]++;
                    }
                    updateStatus();
                }

                @Override
                public void responseDataFail(Object sender, int statusCode, Throwable err, Object errorResponse) {
                    failCount[0]++;
                    updateStatus();
                }

                public void updateStatus(){
                    if (failCount[0] + successCount[0] >= sumUpdate){
                        requestProcess(false);
                        final int sum = sumUpdate;
                        final int success = successCount[0];
                        runOnUiThread(new Runnable() {
                            @Override
                            public void run() {
                                Toast toast = Toast.makeText(myActivity, "保存 「" + success + "/" + sum + "」 しました。", Toast.LENGTH_LONG);
                                toast.setGravity(Gravity.TOP|Gravity.CENTER_HORIZONTAL, 0, 0);
                                toast.show();

                                updateTableView(listProduce, colWidthPersent, colLabel, screenWidth, linearLayoutParent);
                            }
                        });
                    }
                }
            });
        }

    }

    private String formatSearchString(String value){
        int lent = value.length();
        if (lent == 0) return "";

        int maxLen = limitItemCd;
        String result = value;
        for (int i = 0; i < maxLen - lent; i++){
            result = "0"+result;
        }
        return result;
    }

}
